#include "encoder_knobs.h"
#include <stdlib.h>
#include <math.h>

static EncoderSystem system;


static void process_rotation(EncoderEntity *e) {
    uint8_t a = hal_gpio_read(e->config.pin_a);
    uint8_t b = hal_gpio_read(e->config.pin_b);
    if(a != e->state.last_a || b != e->state.last_b) {
        // 方向检测
        uint8_t state = (a << 1) | b;
        uint8_t prev_state = (e->state.last_a << 1) | e->state.last_b;
        const int8_t transitions[] = {0, -1, 1, 0, 1, 0, 0, -1, -1, 0, 0, 1};
        int8_t delta = transitions[prev_state * 4 + state];
        if(delta != 0) {
            // 加速度计算
            uint32_t now = system.get_tick();
            if(now - e->accel_sample_time > ACCEL_SAMPLE_MS) {
                e->dynamic.rotation_speed = 0.8 * e->dynamic.rotation_speed + 
                                           0.2 * (1000.0 / (now - e->accel_sample_time));
                e->accel_sample_time = now;
                // 加速度事件处理
                if(e->dynamic.rotation_speed > e->config.accel_threshold) {
                    if(!e->dynamic.accel_active) {
                        queue_put(e - system.entities, EVT_ACCELERATION_START, 
                                 (int16_t)e->dynamic.rotation_speed);
                        e->dynamic.accel_active = true;
                    }
                } else {
                    if(e->dynamic.accel_active) {
                        queue_put(e - system.entities, EVT_ACCELERATION_END, 0);
                        e->dynamic.accel_active = false;
                    }
                }
            }
            // 旋转事件入队
            EncoderEventType type = (delta > 0) ? EVT_ROTATION_CW : EVT_ROTATION_CCW;
            queue_put(e - system.entities, type, 1);
        }
        e->state.last_a = a;
        e->state.last_b = b;
    }
}

static void process_button(EncoderEntity *e) {
    uint8_t btn = hal_gpio_read(e->config.pin_btn);
    uint32_t now = system.get_tick();
    // 状态机处理按钮事件
    switch(e->state.btn_state) {
        case 0: // 初始状态
            if(btn == e->config.active_level) {
                e->state.btn_state = 1;
                e->btn_down_time = now;
            }
            break;
            
        case 1: // 按下消抖中
            if(now - e->btn_down_time > e->config.debounce_ms) {
                if(btn == e->config.active_level) {
                    e->state.btn_state = 2; // 确认按下
                } else {
                    e->state.btn_state = 0; // 误触发复位
                }
            }
            break;
            
        case 2: // 持续按下状态
            if(btn != e->config.active_level) {
                e->state.btn_state = 3;
                e->last_release_time = now;
                
                // 处理长按
                if(now - e->btn_down_time >= e->config.longpress_ms) {
                    queue_put(e - system.entities, EVT_BUTTON_LONG, 0);
                }
            } else if(now - e->btn_down_time >= e->config.longpress_ms) {
                queue_put(e - system.entities, EVT_BUTTON_LONG, 0);
            }
            break;
            
        case 3: // 释放消抖中
            if(now - e->last_release_time > e->config.debounce_ms) {
                if(btn != e->config.active_level) {
                    if(e->click_count == 0) {
                        e->click_count++;
                        e->last_release_time = now;
                    } else if((now - e->last_release_time) < e->config.doubleclick_ms) {
                        e->click_count++;
                        queue_put(e - system.entities, EVT_BUTTON_DOUBLE, 0);
                        e->click_count = 0;
                    }
                    e->state.btn_state = 0;
                } else {
                    e->state.btn_state = 2;
                }
            }
            break;
    }
    // 处理单击超时
    if(e->click_count > 0 && (now - e->last_release_time) > e->config.doubleclick_ms) {
        queue_put(e - system.entities, EVT_BUTTON_SHORT, e->click_count);
        e->click_count = 0;
    }
}